/*
 * Chastoslov
 * Copyright (C) 2009 Alexandr Stroghov
 * 
 * stroghov@gmail.com
 * 
 * This program is free software; you can redistribute it and/or modify it under the terms of the 
 * GNU General Public License, version 2, as published by the Free Software Foundation.
 * 
 * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; 
 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 
 * See the GNU General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License along with this program; if 
 * not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, 
 * MA 02111-1307 USA
*/
package world.ah.wf.guiclient;
import java.awt.Frame;
import java.awt.Dimension;
import java.io.FileInputStream;
import javax.swing.ButtonGroup;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JTabbedPane;
import java.awt.BorderLayout;
import javax.swing.JPanel;
import java.awt.FlowLayout;
import javax.swing.JButton;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import javax.swing.JList;
import javax.swing.SwingUtilities;
import javax.swing.UIManager;
import javax.swing.JRadioButton;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.table.DefaultTableModel;
import javax.swing.event.ListSelectionListener;
import javax.swing.event.ListSelectionEvent;
import java.awt.event.WindowEvent;
import java.awt.GridBagLayout;
import java.awt.GridBagConstraints;
import java.awt.Insets;

public class DialogOptions extends JDialog {
  private UIManager.LookAndFeelInfo lf[] = UIManager.getInstalledLookAndFeels();
  private StringTable languageList;
  private String[] langTableColumns = {"Language", "Language"};
  private boolean appearanceChanged = false;
  private boolean languageChanged = false;
  //
  private JTabbedPane tabsOptions = new JTabbedPane();
  private BorderLayout borderLayout1 = new BorderLayout();
  private JPanel pAppearance = new JPanel();
  private JPanel jPanel1 = new JPanel();
  private JButton bClose = new JButton();
  private FlowLayout layoutSouth = new FlowLayout();
  private JButton bApply = new JButton();
  private JButton bOK = new JButton();
  private JList listLookAndFeels = new JList();
  private JRadioButton radioLfDefault = new JRadioButton();
  private JRadioButton radioLfSystem = new JRadioButton();
  private JRadioButton radioLfCustom = new JRadioButton();
  private ButtonGroup groupLfUsegeKind = new ButtonGroup();
  private JScrollPane spAppearance = new JScrollPane();
  
  public DialogOptions() {this(null, "", false);}
  public DialogOptions(Frame parent, String title, boolean modal) {
    super(parent, title, modal);
    try {jbInit();} catch(Exception e) {e.printStackTrace();}
    // МОЯ ИНИЦИАЛИЗАЦИЯ
    tLanguage.getTableHeader().setReorderingAllowed(false);
    General.centerFrame(this);
    // Установка хранителя параметров 
    OptionsHolder opt = General.optionsHolder;
    if(opt == null) {
      opt = new OptionsHolder();
      General.optionsHolder = opt;
      ErrorShower.show(this.getParent(), "Program options file didn't exist. Created new.");
    }
    // Установка вкладки внешних видов
    // вариант
    radioLfDefault.setSelected(opt.getLookAndFeelUsageKind() == 
      OptionsHolder.LOOK_AND_FEEL_USE_DEFAULT);
    radioLfSystem.setSelected(opt.getLookAndFeelUsageKind() == 
      OptionsHolder.LOOK_AND_FEEL_USE_SYSTEM);
    radioLfCustom.setSelected(opt.getLookAndFeelUsageKind() == 
      OptionsHolder.LOOK_AND_FEEL_USE_CUSTOM);
    radioLfUsageKind_actionPerformed(null);
    // список
    String[] data = new String[lf.length];
    String currLF = UIManager.getLookAndFeel().getClass().getName();
    String optLF = opt.getLookAndFeelClassName();
    int currLFIndex = -1;
    int optLFIndex = -1;
    for (int i = 0; i < lf.length; i++) {
      data[i] = lf[i].getName();
      String ClassNameI = lf[i].getClassName();
      if(ClassNameI.equals(currLF)) currLFIndex = i;
      if(ClassNameI.equals(optLF)) optLFIndex = i; 
    } 
    listLookAndFeels.setListData(data);
    if(optLFIndex >= 0) listLookAndFeels.setSelectedIndex(optLFIndex);    
    else if(currLFIndex >= 0) listLookAndFeels.setSelectedIndex(currLFIndex); 
    // c внешними видами все
    // Список языков 
    languageList = new StringTable(3);
    languageList.clear();
    try {languageList.load(new FileInputStream("wfLanguages.csv"));}     
    catch (Exception ex) {ErrorShower.show(this, "language list loading", "", ex);} 
    tLanguage.setModel(new DefaultTableModel(languageList.toStringArray(), langTableColumns) {
      public boolean isCellEditable(int row, int column) {return false;}
      public String getColumnName(int column) {return langTableColumns[column];}
    });
    int curLangRow = languageList.getRowOf(1, General.getLanguageCode());
    tLanguage.changeSelection(curLangRow, 0, false, false);
    // будем реагировать на изменение строки
    tLanguage.getSelectionModel().addListSelectionListener(new ListSelectionListener() {
      public void valueChanged(ListSelectionEvent ev) {
        languageChanged = true;
        setModified(true);
      }
    });
    //
    setModified(false);
    // Язык
    setLang();
    //
  }

  private void jbInit() throws Exception {
    this.setSize(new Dimension(425, 336));
    this.getContentPane().setLayout(borderLayout1);
    this.setTitle("Options");
    this.setResizable(false);
    this.setModal(true);
    this.setDefaultCloseOperation(0);
    this.addWindowListener(new java.awt.event.WindowAdapter()
      {
        public void windowClosing(WindowEvent e)
        {
          this_windowClosing(e);
        }
      });
    pAppearance.setLayout(gridBagLayout2);
    jPanel1.setLayout(layoutSouth);
    bClose.setText("Close");
    bClose.addActionListener(new ActionListener()
      {
        public void actionPerformed(ActionEvent e)
        {
          bCancel_actionPerformed(e);
        }
      });
    layoutSouth.setAlignment(2);
    layoutSouth.setHgap(10);
    layoutSouth.setVgap(10);
    bApply.setText("Apply");
    bApply.addActionListener(new ActionListener()
      {
        public void actionPerformed(ActionEvent e)
        {
          bApply1_actionPerformed(e);
        }
      });
    bOK.setText("OK");
    bOK.addActionListener(new ActionListener()
      {
        public void actionPerformed(ActionEvent e)
        {
          bOK_actionPerformed(e);
        }
      });
    listLookAndFeels.addListSelectionListener(new ListSelectionListener()
      {
        public void valueChanged(ListSelectionEvent e)
        {
          listLookAndFeels_valueChanged(e);
        }
      });
    radioLfDefault.setText("Default");
    radioLfDefault.addActionListener(radioLfUsageKindListiner);
    radioLfSystem.setText("System");
    radioLfSystem.addActionListener(radioLfUsageKindListiner);
    radioLfCustom.setText("Custom");
    radioLfCustom.addActionListener(radioLfUsageKindListiner);
    pLanguage.setLayout(gridBagLayout1);
    pAppearanceType.setLayout(layoutAppearanceType);
    layoutAppearanceType.setHgap(10);
    layoutAppearanceType.setVgap(10);
    spAppearance.getViewport().add(listLookAndFeels, null);
    pAppearance.add(spAppearance, new GridBagConstraints(0, 1, 1, 1, 1.0, 1.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0, 10, 10, 10), 0, 0));
    pAppearanceType.add(radioLfDefault, null);
    pAppearanceType.add(radioLfSystem, null);
    pAppearanceType.add(radioLfCustom, null);
    pAppearance.add(pAppearanceType, new GridBagConstraints(0, 0, 1, 1, 1.0, 0.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(0, 0, 0, 0), 0, 0));
    spLanguage.getViewport().add(tLanguage, null);
    pLanguage.add(spLanguage, new GridBagConstraints(0, 0, 1, 1, 1.0, 1.0, GridBagConstraints.CENTER, GridBagConstraints.BOTH, new Insets(10, 10, 10, 10), 0, 0));
    tabsOptions.addTab("Appearance", pAppearance);
    tabsOptions.addTab("Language", pLanguage);
    this.getContentPane().add(tabsOptions, BorderLayout.CENTER);
    jPanel1.add(bOK, null);
    jPanel1.add(bClose, null);
    jPanel1.add(bApply, null);
    this.getContentPane().add(jPanel1, BorderLayout.SOUTH);
    groupLfUsegeKind.add(radioLfDefault);
    groupLfUsegeKind.add(radioLfSystem);
    groupLfUsegeKind.add(radioLfCustom);
  }
  /** Устанавливает язык интерфейса */
  public void setLang() {
    String s;
    s = General.getLangItem("Options"); if(s.length() > 0) this.setTitle(s);
    // Заголовки вкладок 
    for(int i = 0; i < tabsOptions.getTabCount(); i++)
      if(tabsOptions.getComponentAt(i) == pAppearance) 
        tabsOptions.setTitleAt(i, General.getLangItem("Appearance", tabsOptions.getTitleAt(i)));
      else if(tabsOptions.getComponentAt(i) == pLanguage) 
        tabsOptions.setTitleAt(i, General.getLangItem("Language", tabsOptions.getTitleAt(i)));
    // Кнопки
    s = General.getLangItem("OK"); if(s.length() > 0) bOK.setText(s);
    s = General.getLangItem("Close"); if(s.length() > 0) bClose.setText(s);
    s = General.getLangItem("Apply"); if(s.length() > 0) bApply.setText(s);
    // Варианты внешнего вида 
    s = General.getLangItem("lfDefault"); if(s.length() > 0) radioLfDefault.setText(s);
    s = General.getLangItem("lfSystem"); if(s.length() > 0) radioLfSystem.setText(s);
    s = General.getLangItem("lfCustom"); if(s.length() > 0) radioLfCustom.setText(s);
    // Заголовки таблицы языков 
    langTableColumns[1] = General.getLangItem("Language", langTableColumns[1]);
    //tLanguage.createDefaultColumnsFromModel();
  }
  //
  private void setModified(boolean modified) { 
    if(!modified) {appearanceChanged = false; languageChanged = false;}
    bApply.setEnabled(modified);
  }

  private ActionListener radioLfUsageKindListiner = new ActionListener() {
    public void actionPerformed(ActionEvent ev) {
      radioLfUsageKind_actionPerformed(ev);
    }
  }; 
  private JPanel pLanguage = new JPanel();
  private JScrollPane spLanguage = new JScrollPane();
  private JTable tLanguage = new JTable();
  private GridBagLayout gridBagLayout1 = new GridBagLayout();
  private GridBagLayout gridBagLayout2 = new GridBagLayout();
  private JPanel pAppearanceType = new JPanel();
  private FlowLayout layoutAppearanceType = new FlowLayout();

  private void bCancel_actionPerformed(ActionEvent e) {
    if(bApply.isEnabled()) {
      int confirmResult = JOptionPane.showConfirmDialog(this, General.getLangItem("someWereChanged", 
        "Some of the changed options were not applied. \nDo you want to close the window not " + 
        "applying them?"), General.getLangItem("Question", "Question"), JOptionPane.YES_NO_OPTION); 
      if(confirmResult == JOptionPane.YES_OPTION) this.setVisible(false);
    } else this.setVisible(false);
  }

  private void bOK_actionPerformed(ActionEvent ev) {
    bApply1_actionPerformed(ev);
    if(!bApply.isEnabled()) this.setVisible(false);
  }

  private void radioLfUsageKind_actionPerformed(ActionEvent e) {
    listLookAndFeels.setEnabled(radioLfCustom.isSelected());
    appearanceChanged = true;
    setModified(true);
  }
  
  // ПРИМЕНЕНИЕ ИЗМЕНЕНИЙ
  private void bApply1_actionPerformed(ActionEvent e) {
    OptionsHolder opt = General.optionsHolder;
    boolean restartNeededToComplete = false;
    // Внешний вид 
    if(appearanceChanged) {
      int i = listLookAndFeels.getSelectedIndex();
      if(radioLfDefault.isSelected()) opt.setLookAndFeelUsageKind(0);
      else if(radioLfSystem.isSelected()) opt.setLookAndFeelUsageKind(1);
      else if(radioLfCustom.isSelected()) {
        opt.setLookAndFeelUsageKind(2);
        if(i < 0) {i = 0; listLookAndFeels.setSelectedIndex(i);}
      };
      if(i < 0) opt.setLookAndFeelClassName("");
      else opt.setLookAndFeelClassName(lf[i].getClassName());
      General.setLookAndFeelFromOptions();
      SwingUtilities.updateComponentTreeUI(this.getContentPane());
      SwingUtilities.updateComponentTreeUI(((JFrame)(this.getParent())).getContentPane());
      restartNeededToComplete = true;
    }
    // Язык 
    if(languageChanged) {
      int chosenLang = tLanguage.getSelectedRow();
      //System.out.println("getSelectedRow() = " + Integer.toString(chosenLang));
      if(chosenLang < 0) opt.setLanguageFileName("");
      else opt.setLanguageFileName(languageList.get(chosenLang, 2));
      try {General.loadLanguageFile(opt.getLanguageFileName());}
      catch (Exception ex) {ErrorShower.show(null, "language file loading", "", ex); return;}
      this.setLang();
      ((MainForm)this.getParent()).setLang();
      restartNeededToComplete = true;
    }
    //
    try {opt.saveProperties(); setModified(false);}
    catch (Exception ex) {ErrorShower.show(this, "saving program options", "", ex); return;}
    //
    if(restartNeededToComplete) JOptionPane.showMessageDialog(this, 
      General.getLangItem("restartNeededToComplete", "Some of the parameters changed \n" + 
      "will be completely applied only after the program restart"), General.getLangItem("Warning", 
      "Warning"), JOptionPane.WARNING_MESSAGE); 
  }

  private void listLookAndFeels_valueChanged(ListSelectionEvent e) {
    appearanceChanged = true;
    setModified(true);
  }

  private void this_windowClosing(WindowEvent e) {
    bCancel_actionPerformed(null);
  }
  
  
  
  
  
  
}